﻿/* ***********************************************
 * Author		:  kingthy
 * Email		:  kingthy@gmail.com
 * Description	:  DbHelper
 *
 * ***********************************************/

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.Common;
using System.Data;
using System.Data.OleDb;
using System.Data.SqlClient;
using System.Data.Odbc;
using KT.Core.Extensions;
namespace KT.Framework.Database
{
    /// <summary>
    /// 数据库帮助对象，用于执行相关的命令
    /// </summary>
    public class DbHelper : IDisposable
    {
        #region 构造函数
        /// <summary>
        /// 根据DbConnection实例化对象
        /// </summary>
        /// <param name="connection">数据库连接对象</param>
        public DbHelper(DbConnection connection) : this(connection, false)
        {
        }
        /// <summary>
        /// 根据DbConnection及是否保持连接状态参数实例化对象
        /// </summary>
        /// <param name="connection">数据库连接对象</param>
        /// <param name="keepConnection">是否保持数据源的连接状态。如果true则连接被打开后不会自动关闭</param>
        public DbHelper(DbConnection connection, bool keepConnection)
        {
            this.ChangeDbConnection(connection, keepConnection);
        }
        #endregion

        #region 处理数据库连接
        /// <summary>
        /// 返回当前的数据库的连接对象实例
        /// </summary>
        public DbConnection Connection { get; protected set; }
        /// <summary>
        /// 更改数据连接
        /// </summary>
        /// <param name="connection">新的数据库连接对象</param>
        public void ChangeDbConnection(DbConnection connection)
        {
            this.ChangeDbConnection(connection, false);
        }
        /// <summary>
        /// 更改数据连接
        /// </summary>
        /// <param name="connection">新的数据库连接对象</param>
        /// <param name="keepConnection">是否保持数据源的连接状态。如果true则连接被打开后不会自动关闭</param>
        public void ChangeDbConnection(DbConnection connection, bool keepConnection)
        {
            this.Connection = connection;
            this.KeepConnection = keepConnection;
            this.DbTransaction = null;
            this.OnDbConnectionReset();
        }
        /// <summary>
        /// 打开数据连接
        /// </summary>
        /// <param name="connection"></param>
        internal void OpenConnection(DbConnection connection)
        {
            if (connection.State == ConnectionState.Closed)
                connection.Open();
        }
        /// <summary>
        /// 关闭数据连接
        /// </summary>
        /// <param name="connection"></param>
        protected void CloseConnection(DbConnection connection)
        {
            if (connection != null)
            {
                if (connection.State != ConnectionState.Closed)
                {
                    this.Connection.Close();
                }
            }
        }
        /// <summary>
        /// 打开当前的数据库连接
        /// </summary>
        public void Open()
        {
            this.OpenConnection(this.Connection);
        }
        /// <summary>
        /// 关闭当前已连接的数据库连接
        /// </summary>
        public void Close()
        {
            this.CloseConnection(this.Connection);
        }

        /// <summary>
        /// 数据连接已重置
        /// </summary>
        private void OnDbConnectionReset()
        {
            if (this.IdentifierFormatter != null)
            {
                this.IdentifierFormatter.Dispose();
            }
            this.IdentifierFormatter = null;
            this.ConnectionDbProviderFactory = null;
        }
        #endregion

        #region 处理事务
        /// <summary>
        /// 事务的连接对象是否是关闭状态的
        /// </summary>
        private bool DbTransactionConnectionIsClosed = false;
        /// <summary>
        /// 当前事务是否是由当前的数据库连接对象生成的
        /// </summary>
        public bool DbTransactionIsCreatedByDbConnection { get; private set; }
        /// <summary>
        /// 
        /// </summary>
        private DbTransaction _DbTransaction;
        /// <summary>
        /// 返回或设置当前执行的命令所用的事务
        /// </summary>
        public DbTransaction DbTransaction
        {
            get
            {
                return this._DbTransaction;
            }
            set
            {
                this._DbTransaction = value;
                this.DbTransactionIsCreatedByDbConnection = false;
                this.OnDbConnectionReset();
            }
        }

        /// <summary>
        /// 启动事务
        /// </summary>
        public DbTransaction BeginTransaction()
        {
            if (this._DbTransaction == null)
            {
                this.DbTransactionConnectionIsClosed = false;
                if (this.Connection.State == ConnectionState.Closed)
                {
                    this.DbTransactionConnectionIsClosed = true;
                    this.OpenConnection(this.Connection);
                }
                this._DbTransaction = this.Connection.BeginTransaction();
                this.DbTransactionIsCreatedByDbConnection = true;
            }
            return this._DbTransaction;
        }
        /// <summary>
        /// 启动事务
        /// </summary>
        /// <param name="il"></param>
        public DbTransaction BeginTransaction(IsolationLevel il)
        {
            if (this._DbTransaction == null)
            {
                this.DbTransactionConnectionIsClosed = false;
                if (this.Connection.State == ConnectionState.Closed)
                {
                    this.DbTransactionConnectionIsClosed = true;
                    this.OpenConnection(this.Connection);
                }
                this._DbTransaction = this.Connection.BeginTransaction(il);
                this.DbTransactionIsCreatedByDbConnection = true;
            }
            return this._DbTransaction;
        }

        /// <summary>
        /// 提交事务
        /// </summary>
        public void CommitTransaction()
        {
            if (this.DbTransaction != null)
            {
                this.DbTransaction.Commit();
                this.RecycleTransaction();
            }
        }

        /// <summary>
        /// 回滚事务
        /// </summary>
        public void RollbackTransaction()
        {
            if (this.DbTransaction != null)
            {
                this.DbTransaction.Rollback();
                this.RecycleTransaction();
            }
        }

        /// <summary>
        /// 回收事务
        /// </summary>
        protected void RecycleTransaction()
        {
            //只有事务是当前连接对象生成的才进行回收
            if (this.DbTransactionIsCreatedByDbConnection)
            {
                if (this.DbTransactionConnectionIsClosed)
                {
                    if (!this.KeepConnection)
                        this.CloseConnection(this.DbTransaction.Connection);
                }

                this.DbTransaction.Dispose();
            }
            this.DbTransaction = null;
        }
        #endregion

        #region 是否保持打开状态
        /// <summary>
        /// 是否保持数据连接的连接状态。如果值为true则数据源被打开后不自动关闭。
        /// 否则每次运行完语句后自动恢复数据连接的原状(如果原连接是关闭状态则运行完语句后关闭连接；如果原连接是打开状态则运行完语句后保持打开状态）
        /// </summary>
        public bool KeepConnection
        {
            get;
            internal set;
        }
        #endregion

        #region 获取查询命令
        /// <summary>
        /// 生成一个新的DbCommand
        /// </summary>
        /// <returns></returns>
        public DbCommand CreateDbCommand()
        {
            DbCommand command = null;
            DbConnection connection = this.Connection;
            if (this.DbTransaction != null)
            {
                connection = this.DbTransaction.Connection;
                command = connection.CreateCommand();
                command.Transaction = this.DbTransaction;
            }
            else
            {
                command = connection.CreateCommand();
            }
            if(connection.ConnectionTimeout > command.CommandTimeout)
                command.CommandTimeout = connection.ConnectionTimeout;
            return command;
        }
        /// <summary>
        /// 生成一个新的DbCommand
        /// </summary>
        /// <param name="commandText">命令语句</param>
        /// <returns></returns>
        public DbCommand CreateDbCommand(string commandText)
        {
            return this.CreateDbCommand(CommandType.Text, commandText, null);
        }
        /// <summary>
        /// 生成一个新的DbCommand
        /// </summary>
        /// <param name="commandType">命令类型</param>
        /// <param name="commandText">命令语句</param>
        /// <returns></returns>
        public DbCommand CreateDbCommand(CommandType commandType, string commandText)
        {
            return this.CreateDbCommand(commandType, commandText, null);
        }
        /// <summary>
        /// 生成一个新的DbCommand
        /// </summary>
        /// <param name="commandText">命令语句</param>
        /// <param name="parameters">命令参数</param>
        /// <returns></returns>
        public DbCommand CreateDbCommand(string commandText, params DbParameter[] parameters)
        {
            return this.CreateDbCommand(CommandType.Text, commandText, parameters);
        }
        /// <summary>
        /// 生成一个新的DbCommand
        /// </summary>
        /// <param name="commandType">命令类型</param>
        /// <param name="commandText">命令语句</param>
        /// <param name="parameters">命令参数</param>
        /// <returns></returns>
        public DbCommand CreateDbCommand(CommandType commandType, string commandText, params DbParameter[] parameters)
        {
            var command = this.CreateDbCommand();
            command.CommandType = commandType;
            command.CommandText = commandText;
            if (parameters != null)
            {
                foreach (DbParameter par in parameters)
                {
                    if (par != null)
                    {
                        if (command.Parameters.Contains(par.ParameterName))
                        {
                            command.Parameters[par.ParameterName] = par;
                        }
                        else
                        {
                            command.Parameters.Add(par);
                        }
                    }
                }
            }
            return command;
        }

        /// <summary>
        /// 生成一个新的已包装过的查询命令
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        private DbCommandWrapped CreateDbCommandWrapped(DbCommand command)
        {
            return DbCommandWrapped.Create(command, this.KeepConnection);
        }
        /// <summary>
        /// 生成一个新的已包装过的查询命令
        /// </summary>
        /// <param name="commandText">查询语句</param>
        /// <returns></returns>
        public DbCommandWrapped CreateDbCommandWrapped(string commandText)
        {
            return this.CreateDbCommandWrapped(this.CreateDbCommand(commandText));
        }
        /// <summary>
        /// 生成一个新的已包装过的查询命令
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public DbCommandWrapped CreateDbCommandWrapped(CommandType commandType, string commandText)
        {
            return this.CreateDbCommandWrapped(this.CreateDbCommand(commandType, commandText));
        }
        /// <summary>
        /// 生成一个新的已包装过的查询命令
        /// </summary>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public DbCommandWrapped CreateDbCommandWrapped(string commandText, params DbParameter[] parameters)
        {
            return this.CreateDbCommandWrapped(this.CreateDbCommand(commandText, parameters));
        }
        /// <summary>
        /// 生成一个新的已包装过的查询命令
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public DbCommandWrapped CreateDbCommandWrapped(CommandType commandType, string commandText, params DbParameter[] parameters)
        {
            return this.CreateDbCommandWrapped(this.CreateDbCommand(commandType, commandText, parameters));
        }
        #endregion

        #region 标识符处理
        /// <summary>
        /// 用于处理标识符数据的命令对象
        /// </summary>
        private System.Data.Common.DbCommandBuilder IdentifierFormatter;
        /// <summary>
        /// 获取用于处理标识符数据的命令对象
        /// </summary>
        /// <returns></returns>
        private System.Data.Common.DbCommandBuilder GetIdentifierFormatter()
        {
            if (this.IdentifierFormatter == null)
            {
                var f = this.GetDbProviderFactory();
                this.IdentifierFormatter = f.CreateCommandBuilder();
                this.IdentifierFormatter.DataAdapter = f.CreateDataAdapter();
                this.IdentifierFormatter.DataAdapter.SelectCommand = this.CreateDbCommand();
            }
            var command = this.IdentifierFormatter.DataAdapter == null ? null : this.IdentifierFormatter.DataAdapter.SelectCommand;
            if (command != null && command.Connection != null)
            {
                if (typeof(OleDbConnection).IsInstanceOfType(command.Connection)
                    || typeof(OdbcConnection).IsInstanceOfType(command.Connection))
                {
                    this.OpenConnection(command.Connection);
                }
            }
            return this.IdentifierFormatter;
        }

        /// <summary>
        /// 对标识符（如表名、列名）进行处理
        /// </summary>
        /// <param name="unquotedIdentifier"></param>
        /// <returns></returns>
        public virtual string QuoteIdentifier(string unquotedIdentifier)
        {
            return this.GetIdentifierFormatter().QuoteIdentifier(unquotedIdentifier);
        }

        /// <summary>
        /// 对字符数据进行转义，比如在Sql server里对单引号“'”进行转义处理
        /// </summary>
        /// <param name="value">需要转义的字符数据</param>
        /// <returns></returns>
        public virtual string EscapeString(string value)
        {
            if (string.IsNullOrEmpty(value)) return string.Empty;

            int p = -1;
            for (var i = 0; i < value.Length; i++)
            {
                if (value[i] == '\'')
                {
                    p = i;
                    break;
                }
            }
            if (p == -1) return value;  //不需要转义
            StringBuilder buffer = new StringBuilder(value.Substring(0, p));
            buffer.Append("''");
            for (var i = p + 1; i < value.Length; i++)
            {
                char c = value[i];
                if (c == '\'')
                {
                    buffer.Append('\'');
                }
                buffer.Append(c);
            }
            return buffer.ToString();
        }
        #endregion

        #region 构造命令参数
        /// <summary>
        /// 获取带前缀的参数名称
        /// </summary>
        /// <param name="name">源名称,不带前缀</param>
        /// <returns></returns>
        public virtual string GetDbParameterName(string name)
        {
            return name.StartsWith("@") ? name : string.Concat("@", name);
        }

        /// <summary>
        /// 获取参数的值
        /// </summary>
        /// <param name="value"></param>
        /// <param name="dbType"></param>
        protected virtual object GetDbParameterValue(object value, DbType dbType)
        {
            if (value == null) return DBNull.Value;
            if (value is DateTime)
            {
                var t = (DateTime)value;
                if (t == DateTime.MinValue || t == DateTime.MaxValue) return DBNull.Value;

                return value.ToString();
            }
            return value;
        }

        /// <summary>
        /// 获取一个新的命令参数
        /// </summary>
        /// <param name="name">参数名称，不带前缀</param>
        /// <returns></returns>
        public DbParameter CreateDbParameter(string name)
        {
            var par = this.GetDbProviderFactory().CreateParameter();
            par.ParameterName = this.GetDbParameterName(name);
            return par;
        }
        /// <summary>
        /// 获取一个新的命令参数
        /// </summary>
        /// <param name="name">参数名，不带前缀</param>
        /// <param name="value">参数的值</param>
        /// <returns></returns>
        public DbParameter CreateDbParameter(string name, object value)
        {
            var par = this.CreateDbParameter(name);
            par.Value = this.GetDbParameterValue(value, DbType.Object);
            return par;
        }
        /// <summary>
        /// 获取一个新的命令参数
        /// </summary>
        /// <param name="name">参数名，不带前缀</param>
        /// <param name="dbType">参数类型</param>
        /// <param name="value">参数的值</param>
        /// <returns></returns>
        public DbParameter CreateDbParameter(string name, DbType dbType, object value)
        {
            var par = this.CreateDbParameter(name);
            par.DbType = dbType;
            par.Value = this.GetDbParameterValue(value, dbType);
            return par;
        }
        /// <summary>
        /// 获取一个新的命令参数
        /// </summary>
        /// <param name="name">参数名，不带前缀</param>
        /// <param name="dbType">参数类型</param>
        /// <param name="direction">参数访问类型</param>
        /// <param name="value">参数的值</param>
        /// <returns></returns>
        public DbParameter CreateDbParameter(string name, DbType dbType, ParameterDirection direction, object value)
        {
            var par = this.CreateDbParameter(name);
            par.DbType = dbType;
            par.Direction = direction;
            par.Value = this.GetDbParameterValue(value, dbType);
            return par;
        }
        /// <summary>
        /// 获取一个新的命令参数
        /// </summary>
        /// <param name="name">参数名，不带前缀</param>
        /// <param name="dbType">参数类型</param>
        /// <param name="size">参数大小</param>
        /// <param name="value">参数的值</param>
        /// <returns></returns>
        public DbParameter CreateDbParameter(string name, DbType dbType, int size, object value)
        {
            var par = this.CreateDbParameter(name);
            par.DbType = dbType;
            par.Size = size;
            par.Value = this.GetDbParameterValue(value, dbType);
            return par;
        }
        /// <summary>
        /// 获取一个新的命令参数
        /// </summary>
        /// <param name="name">参数名，不带前缀</param>
        /// <param name="dbType">参数类型</param>
        /// <param name="size">参数大小</param>
        /// <param name="direction">参数访问类型</param>
        /// <param name="value">参数的值</param>
        /// <returns></returns>
        public DbParameter CreateDbParameter(string name, DbType dbType, int size, ParameterDirection direction, object value)
        {
            var par = this.CreateDbParameter(name);
            par.DbType = dbType;
            par.Size = size;
            par.Direction = direction;
            par.Value = this.GetDbParameterValue(value, dbType);
            return par;
        }
        #endregion

        #region 获取DataAdapter实例
        /// <summary>
        /// 连接对应的数据驱动工厂
        /// </summary>
        private DbProviderFactory ConnectionDbProviderFactory;
        /// <summary>
        /// 获取当前执行的connection对应的数据驱动实例
        /// </summary>
        /// <returns></returns>
        protected virtual DbProviderFactory GetDbProviderFactory()
        {
            if (this.ConnectionDbProviderFactory == null)
            {
                var connection = this.Connection;
                if (this.DbTransaction != null)
                {
                    connection = this.DbTransaction.Connection;
                }

                this.ConnectionDbProviderFactory = GetDbProviderFactory(connection);
            }
            return this.ConnectionDbProviderFactory;
        }
        /// <summary>
        /// 获取connection对应的数据驱动实例
        /// </summary>
        /// <param name="connection"></param>
        /// <returns></returns>
        public static DbProviderFactory GetDbProviderFactory(DbConnection connection)
        {
            if (typeof(SqlConnection).IsInstanceOfType(connection)) return SqlClientFactory.Instance;
            if (typeof(OleDbConnection).IsInstanceOfType(connection)) return OleDbFactory.Instance;
            if (typeof(OdbcConnection).IsInstanceOfType(connection)) return OdbcFactory.Instance;

            var type = connection.GetType();
            var property = type.GetProperty("DbProviderFactory", System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic);
            return property.GetValue(connection, null).As<DbProviderFactory>();
        }

        /// <summary>
        /// 获取DataAdapter实例
        /// </summary>
        /// <param name="command">select语句命令</param>
        /// <returns></returns>
        public virtual DbDataAdapter CreateDbDataAdapter(DbCommand command)
        {
            var factory = GetDbProviderFactory(command.Connection);
            if (factory == null) return null;

            var adapter = factory.CreateDataAdapter();
            adapter.SelectCommand = command;
            return adapter;
        }
        #endregion

        #region 执行命令 ExecuteNonQuery
        /// <summary>
        /// 执行命令语句
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        protected int ExecuteNonQuery(DbCommandWrapped command)
        {
            using (command)
            {
                return command.ExecuteNonQuery();
            }
        }
        /// <summary>
        /// 执行命令语句
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        public int ExecuteNonQuery(DbCommand command)
        {
            bool isClosed = command.Connection.State == ConnectionState.Closed;

            if (isClosed) this.OpenConnection(command.Connection);

            int r = command.ExecuteNonQuery();

            if (isClosed) command.Connection.Close();

            return r;
        }
        /// <summary>
        /// 执行命令语句
        /// </summary>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public int ExecuteNonQuery(string commandText)
        {
            return this.ExecuteNonQuery(this.CreateDbCommandWrapped(commandText));
        }
        /// <summary>
        /// 执行命令语句
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public int ExecuteNonQuery(CommandType commandType, string commandText)
        {
            return this.ExecuteNonQuery(this.CreateDbCommandWrapped(commandType, commandText));
        }
        /// <summary>
        /// 执行命令语句
        /// </summary>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public int ExecuteNonQuery(string commandText, params DbParameter[] parameters)
        {
            return this.ExecuteNonQuery(this.CreateDbCommandWrapped(commandText, parameters));
        }
        /// <summary>
        /// 执行命令语句
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public int ExecuteNonQuery(CommandType commandType, string commandText, params DbParameter[] parameters)
        {
            return this.ExecuteNonQuery(this.CreateDbCommandWrapped(commandType, commandText, parameters));
        }
        #endregion

        #region 执行命令 ExecuteScalar
        /// <summary>
        /// 执行命令语句,并返回第一行第一列的数据
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        protected object ExecuteScalar(DbCommandWrapped command)
        {
            using (command)
            {
                return command.ExecuteScalar();
            }
        }
        /// <summary>
        /// 执行命令语句,并返回第一行第一列的数据
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        public object ExecuteScalar(DbCommand command)
        {
            bool isClosed = command.Connection.State == ConnectionState.Closed;

            if (isClosed) this.OpenConnection(command.Connection);

            object r = command.ExecuteScalar();

            if (isClosed) command.Connection.Close();

            return r;
        }
        /// <summary>
        /// 执行命令语句,并返回第一行第一列的数据
        /// </summary>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public object ExecuteScalar(string commandText)
        {
            return this.ExecuteScalar(this.CreateDbCommandWrapped(commandText));
        }
        /// <summary>
        /// 执行命令语句,并返回第一行第一列的数据
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public object ExecuteScalar(CommandType commandType, string commandText)
        {
            return this.ExecuteScalar(this.CreateDbCommandWrapped(commandType, commandText));
        }
        /// <summary>
        /// 执行命令语句,并返回第一行第一列的数据
        /// </summary>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public object ExecuteScalar(string commandText, params DbParameter[] parameters)
        {
            return this.ExecuteScalar(this.CreateDbCommandWrapped(commandText, parameters));
        }
        /// <summary>
        /// 执行命令语句,并返回第一行第一列的数据
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public object ExecuteScalar(CommandType commandType, string commandText, params DbParameter[] parameters)
        {
            return this.ExecuteScalar(this.CreateDbCommandWrapped(commandType, commandText, parameters));
        }
        #endregion

        #region 执行命令 ExecuteReader
        /// <summary>
        /// 执行命令语句，并返回数据流
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        protected virtual DbDataReader ExecuteReader(DbCommandWrapped command)
        {
            using (command)
            {
                return command.ExecuteReader();
            }
        }

        /// <summary>
        /// 执行命令语句，并返回数据流
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        public DbDataReader ExecuteReader(DbCommand command)
        {
            bool isClosed = command.Connection.State == ConnectionState.Closed;

            if (isClosed) this.OpenConnection(command.Connection);

            return command.ExecuteReader((isClosed ?
                CommandBehavior.CloseConnection : CommandBehavior.Default));
        }

        /// <summary>
        /// 执行命令语句，并返回数据流
        /// </summary>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public DbDataReader ExecuteReader(string commandText)
        {
            return this.ExecuteReader(this.CreateDbCommandWrapped(commandText));
        }
        /// <summary>
        /// 执行命令语句，并返回数据流
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public DbDataReader ExecuteReader(CommandType commandType, string commandText)
        {
            return this.ExecuteReader(this.CreateDbCommandWrapped(commandType, commandText));
        }
        /// <summary>
        /// 执行命令语句，并返回数据流
        /// </summary>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public DbDataReader ExecuteReader(string commandText, params DbParameter[] parameters)
        {
            return this.ExecuteReader(this.CreateDbCommandWrapped(commandText, parameters));
        }
        /// <summary>
        /// 执行命令语句，并返回数据流
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public DbDataReader ExecuteReader(CommandType commandType, string commandText, params DbParameter[] parameters)
        {
            return this.ExecuteReader(this.CreateDbCommandWrapped(commandType, commandText, parameters));
        }
        #endregion

        #region 执行命令 ExecuteDataSet
        /// <summary>
        /// 执行命令语句,并返回DataSet内存表
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        protected DataSet ExecuteDataSet(DbCommandWrapped command)
        {
            DataSet dataset = new DataSet();
            this.FillDataSet(dataset, command);
            return dataset;
        }
        /// <summary>
        /// 执行命令语句,并返回DataSet内存表
        /// </summary>
        /// <param name="command"></param>
        /// <returns></returns>
        public DataSet ExecuteDataSet(DbCommand command)
        {
            DataSet dataset = new DataSet();
            this.FillDataSet(dataset, command);

            return dataset;
        }
        /// <summary>
        /// 执行命令语句,并返回DataSet内存表
        /// </summary>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public DataSet ExecuteDataSet(string commandText)
        {
            return this.ExecuteDataSet(this.CreateDbCommandWrapped(commandText));
        }
        /// <summary>
        /// 执行命令语句,并返回DataSet内存表
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public DataSet ExecuteDataSet(CommandType commandType, string commandText)
        {
            return this.ExecuteDataSet(this.CreateDbCommandWrapped(commandType, commandText));
        }
        /// <summary>
        /// 执行命令语句,并返回DataSet内存表
        /// </summary>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public DataSet ExecuteDataSet(string commandText, DbParameter[] parameters)
        {
            return this.ExecuteDataSet(this.CreateDbCommandWrapped(commandText, parameters));
        }
        /// <summary>
        /// 执行命令语句,并返回DataSet内存表
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public DataSet ExecuteDataSet(CommandType commandType, string commandText, DbParameter[] parameters)
        {
            return this.ExecuteDataSet(this.CreateDbCommandWrapped(commandType, commandText, parameters));
        }
        #endregion

        #region 执行命令 ExecuteDbObject<T>
        /// <summary>
        /// 执行命令语句,并返回一个数据对象对象
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="command"></param>
        /// <returns></returns>
        protected T ExecuteDbObject<T>(DbCommandWrapped command)
            where T : DbObject, new()
        {
            using (var reader = this.ExecuteReader(command))
            {
                if (reader.Read())
                {
                    return reader.ToDbObject<T>();
                }
                else
                {
                    return default(T);
                }
            }
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象对象
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="command"></param>
        /// <returns></returns>
        public T ExecuteDbObject<T>(DbCommand command)
            where T : DbObject, new()
        {
            using (var reader = this.ExecuteReader(command))
            {
                if (reader.Read())
                {
                    return reader.ToDbObject<T>();
                }
                else
                {
                    return default(T);
                }
            }
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象对象
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public T ExecuteDbObject<T>(string commandText)
                where T : DbObject, new()
        {
            return this.ExecuteDbObject<T>(this.CreateDbCommandWrapped(commandText));
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象对象
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public T ExecuteDbObject<T>(CommandType commandType, string commandText)
                where T : DbObject, new()
        {
            return this.ExecuteDbObject<T>(this.CreateDbCommandWrapped(commandType, commandText));
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象对象
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public T ExecuteDbObject<T>(string commandText, params DbParameter[] parameters)
                where T : DbObject, new()
        {
            return this.ExecuteDbObject<T>(this.CreateDbCommandWrapped(commandText, parameters));
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象对象
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public T ExecuteDbObject<T>(CommandType commandType, string commandText, params DbParameter[] parameters)
                where T : DbObject, new()
        {
            return this.ExecuteDbObject<T>(this.CreateDbCommandWrapped(commandType, commandText, parameters));
        }
        #endregion

        #region 执行命令 ExecuteDbObjectList<T>
        /// <summary>
        /// 执行命令语句,并返回一个数据对象列表
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="command"></param>
        /// <returns></returns>
        protected List<T> ExecuteDbObjectList<T>(DbCommandWrapped command)
            where T : DbObject, new()
        {
            using (command)
            {
                return command.ExecuteDbObjectList<T>();
            }
        }

        /// <summary>
        /// 执行命令语句,并返回一个数据对象列表
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="command"></param>
        /// <returns></returns>
        public List<T> ExecuteDbObjectList<T>(DbCommand command)
            where T : DbObject, new()
        {
            using (var reader = this.ExecuteReader(command))
            {
                return reader.ToDbObjectList<T>();
            }
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象列表
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public List<T> ExecuteDbObjectList<T>(string commandText)
                where T : DbObject, new()
        {
            return this.ExecuteDbObjectList<T>(this.CreateDbCommandWrapped(commandText));
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象列表
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public List<T> ExecuteDbObjectList<T>(CommandType commandType, string commandText)
                where T : DbObject, new()
        {
            return this.ExecuteDbObjectList<T>(this.CreateDbCommandWrapped(commandType, commandText));
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象列表
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public List<T> ExecuteDbObjectList<T>(string commandText, params DbParameter[] parameters)
                where T : DbObject, new()
        {
            return this.ExecuteDbObjectList<T>(this.CreateDbCommandWrapped(commandText, parameters));
        }
        /// <summary>
        /// 执行命令语句,并返回一个数据对象列表
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <returns></returns>
        public List<T> ExecuteDbObjectList<T>(CommandType commandType, string commandText, params DbParameter[] parameters)
                where T : DbObject, new()
        {
            return this.ExecuteDbObjectList<T>(this.CreateDbCommandWrapped(commandType, commandText, parameters));
        }
        #endregion

        #region 执行命令 FillDataSet
        /// <summary>
        /// 执行命令语句，并填充DataSet内存表
        /// </summary>
        /// <param name="command"></param>
        /// <param name="dataset"></param>
        /// <returns></returns>
        protected void FillDataSet(DataSet dataset, DbCommandWrapped command)
        {
            using (command)
            {
                using (var adapter = this.CreateDbDataAdapter(command.Command))
                {
                    command.FillDataSet(adapter, dataset);
                }
            }
        }
        /// <summary>
        /// 执行命令语句，并填充DataSet内存表
        /// </summary>
        /// <param name="dataset"></param>
        /// <param name="command"></param>
        /// <returns></returns>
        public void FillDataSet(DataSet dataset, DbCommand command)
        {
            using (var adapter = this.CreateDbDataAdapter(command))
            {
                adapter.Fill(dataset);
            }
        }
        /// <summary>
        /// 执行命令语句，并填充DataSet内存表
        /// </summary>
        /// <param name="dataset"></param>
        /// <param name="commandText"></param>
        /// <returns></returns>
        public void FillDataSet(DataSet dataset, string commandText)
        {
            this.FillDataSet(dataset, this.CreateDbCommandWrapped(commandText));
        }
        /// <summary>
        /// 执行命令语句，并填充DataSet内存表
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="dataset"></param>
        /// <returns></returns>
        public void FillDataSet(DataSet dataset, CommandType commandType, string commandText)
        {
            this.FillDataSet(dataset, this.CreateDbCommandWrapped(commandType, commandText));
        }
        /// <summary>
        /// 执行命令语句，并填充DataSet内存表
        /// </summary>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <param name="dataset"></param>
        /// <returns></returns>
        public void FillDataSet(DataSet dataset,string commandText, params DbParameter[] parameters)
        {
            this.FillDataSet(dataset, this.CreateDbCommandWrapped(commandText, parameters));
        }
        /// <summary>
        /// 执行命令语句，并填充DataSet内存表
        /// </summary>
        /// <param name="commandType"></param>
        /// <param name="commandText"></param>
        /// <param name="parameters"></param>
        /// <param name="dataset"></param>
        /// <returns></returns>
        public void FillDataSet(DataSet dataset, CommandType commandType, string commandText, params DbParameter[] parameters)
        {
            this.FillDataSet(dataset, this.CreateDbCommandWrapped(commandType, commandText, parameters));
        }
        #endregion

        #region 获取数据执行者
        /// <summary>
        /// 生成新的数据执行者
        /// </summary>
        protected virtual DbCommandExecutor CreateDbCommandExecutor()
        {
            return new DbCommandExecutor(this);
        }
        /// <summary>
        /// 数据执行者
        /// </summary>
        private DbCommandExecutor _Executor;
        /// <summary>
        /// 获取数据执行者
        /// </summary>
        public DbCommandExecutor Executor
        {
            get
            {
                if (_Executor == null)
                {
                    _Executor = this.CreateDbCommandExecutor();
                }
                return _Executor;
            }
        }
        #endregion

        #region IDisposable 成员
        /// <summary>
        /// 释放内存资源
        /// </summary>
        public void Dispose()
        {
            if (this.Connection != null)
            {
                this.Close();
                this.Connection.Dispose();
                this.Connection = null;
            }
        }

        #endregion
    }
}
